﻿using Business.BookManagement;
using Business.BookManagement.Dto;
using Business.BorrowManagement.Dto;
using Business.Models;
using Business.Permissions;
using System.Linq.Dynamic.Core;
using Microsoft.AspNetCore.Authorization;
using Microsoft.EntityFrameworkCore;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Volo.Abp.Application.Dtos;
using Volo.Abp.Domain.Repositories;
using Volo.Abp.ObjectMapping;
using XCZ;
using WkHtmlToPdfDotNet;
using Yitter.IdGenerator;
using System.Runtime;
using Business.RGoodManagement.Dto;

namespace Business.BorrowManagement
{
    //[Authorize(BusinessPermissions.BorrowM.Default)]
    public class BorrowAppService : BusinessWorkFlowAppService, IBorrowAppService
    {
        private const string FormName = "BorrowM";
        private IRepository<BorrowM, Guid> _repository;
        private IRepository<BorrowPro, Guid> _repository1;

        private IRepository<RGoods, Guid> _repository3;
        private IRepository<RDetail, Guid> _repository4;



        public BorrowAppService(
            IRepository<BorrowM, Guid> repository, IRepository<BorrowPro, Guid> repository1, IRepository<RGoods, Guid> repository3, IRepository<RDetail, Guid> repository4
            )
        {
            _repository = repository;
            _repository1 = repository1;
            _repository3 = repository3;
            _repository4 = repository4;
        }
        public async Task<BorrowDto> Get(Guid id)
        {
            var query = (from b in await _repository.GetQueryableAsync()
                         where  id == b.Id
                         select new BorrowDto
                         {
                             Id = b.Id,
                             BTitle = b.BTitle,
                             BNum = b.BNum,
                             BPeo = b.BPeo,
                             BTme = b.BTme,
                             BHand = b.BHand,
                             BCon = b.BCon,
                             borrowDetails = (from d in _repository1.GetQueryableAsync().Result
                                              where b.Id == d.BorrowId
                                              select new CreateOrUpdateBorrowDto
                                              {
                                                  PName = d.PName,
                                                  PNum = d.PNum,
                                                  SNum = d.SNum,
                                                  BUnit = d.BUnit,
                                                  BorNum = d.BorNum,
                                              }
                             ).ToList()
                         }
                   ).ToList();



            //var data = await _repository.GetAsync(id);
            //var dto = ObjectMapper.Map<BorrowM, BorrowDto>(data);
            return query.ToList()[0];
        }

        public async Task<PagedResultDto<BorrowDto>> GetAll(GetBorrowInputDto input)
        {
            //var query = (await _repository.GetQueryableAsync()).WhereIf(!string.IsNullOrWhiteSpace(input.Filter), a => a.BTitle.Contains(input.Filter));
            var query = (from b in await _repository.GetQueryableAsync()  
                        // on b.TenantId equals d.BorrowId
                         select new BorrowDto
                         {
                            Id=b.Id,
                            BTitle = b.BTitle,
                            BNum = b.BNum,
                            BPeo = b.BPeo,
                            BTme = b.BTme,
                            BHand = b.BHand,
                            BCon = b.BCon,
                             borrowDetails = (from d in _repository1.GetQueryableAsync().Result
                                              where b.Id == d.BorrowId 
                                              select new CreateOrUpdateBorrowDto
                                              {
                                                  PName = d.PName,
                                                  PNum = d.PNum,
                                                  SNum = d.SNum,
                                                  BUnit = d.BUnit,
                                                  BorNum = d.BorNum,
                                                  GoBit = d.GoBit,
                                                  BitInfo=d.BitInfo,
                                                  GiveTime=d.GiveTime,
                                                  PageStyle=d.PageStyle,
                                                  Desc=d.Desc

                                              }
                             ).ToList()
                         }
                       ).ToList();
            var totalCount = query.Count();
            var items =query.Skip(input.SkipCount - 1).Take(input.MaxResultCount).ToList();
            //var dtos = ObjectMapper.Map<List<BorrowM>, List<BorrowDto>>(items);
            return new PagedResultDto<BorrowDto>(totalCount, query);
        }

        public async Task<BorrowDto> CreateOrUpdate(BorrowDto input)
        {
            BorrowM result = null;
            if (!input.Id.HasValue)
            {
                input.Id = GuidGenerator.Create();
                //雪花Id
                input.BNum = YitIdHelper.NextId().ToString();
                 BorrowM borrow = new BorrowM()
                {
                    BTitle = input.BTitle,
                    BNum=input.BNum,
                    BPeo=input.BPeo,
                    BTme=input.BTme,
                    BHand=input.BHand,
                    BCon = input.BCon

                };
                foreach(var item in input.borrowDetails)
                {
                    BorrowPro detail = new BorrowPro()
                    {
                        BorrowId=input.Id,
                        PName = item.PName,
                        PNum=item.PNum,
                        SNum=item.SNum,
                        BUnit=item.BUnit,
                        BorNum = item.BorNum,
                        GoBit=item.GoBit,
                        BitInfo = item.BitInfo,
                        GiveTime = item.GiveTime,
                        PageStyle = item.PageStyle,
                        Desc = item.Desc,
                    };
                    await _repository1.InsertAsync(detail);

                };
                result = await _repository.InsertAsync(ObjectMapper.Map<BorrowDto, BorrowM>(input));

                //创建工作流
               // await WorkFlow.CreateWorkFlow(FormName, result);
            }
            else
            {
                var data = await _repository.GetAsync(input.Id.Value);

                //BorrowM borrow = new BorrowM()
                //{
                //    BTitle = input.BTitle,
                //    BNum = input.BNum,
                //    BPeo = input.BPeo,
                //    BTme = input.BTme,
                //    BHand = input.BHand,
                //    BCon = input.BCon

                //};
                //borrow=await _repository.UpdateAsync(borrow);
                //foreach (var item in input.borrowDetails)
                //{
                //    BorrowPro detail = new BorrowPro()
                //    {
                //        BorrowId =(Guid) input.Id,
                //        PName = item.PName,
                //        PNum = item.PNum,
                //        SNum = item.SNum,
                //        BUnit = item.BUnit,
                //        BorNum = item.BorNum,
                //        GoBit = item.GoBit,
                //        BitInfo = item.BitInfo,
                //        GiveTime = item.GiveTime,
                //        PageStyle = item.PageStyle,
                //        Desc = item.Desc
                //    };
                //    await _repository1.UpdateAsync(detail);

                //};


                result = await _repository.UpdateAsync(ObjectMapper.Map(input, data));
                //检查流程状态
                //await WorkFlow.CheckFormStatus(input.Id.Value, result);
            }
            return ObjectMapper.Map<BorrowM, BorrowDto>(result);
        }

        public async Task Delete(List<Guid> ids)
        {
            foreach (var item in ids)
            {
                await _repository.DeleteAsync(item);
            }

        }
        public async Task<PagedResultDto<RGoodDto>> GetAllDetail(GetBorrowInputDto input)
        {
            
            var query = (from b in await _repository.GetQueryableAsync()
                            join d in await _repository3.GetQueryableAsync() 
                            on b.Id equals d.BorrowId
                         select new RGoodDto
                         {
                             Id = b.Id,
                             ConUnit = d.ConUnit,
                             Time=b.BTme,
                             RTitle = d.RTitle,
                             RPeo = b.BPeo,
                             RTime = d.RTime,
                             RHand = d.RHand,
                             createOrUpdateRGoodDto = (from a in _repository1.GetQueryableAsync().Result
                                                       join c in _repository4.GetQueryableAsync().Result
                                                       on a.PName equals c.RPName
                                                       
                                              where c.RGoodId == d.Id
                                              select new CreateOrUpdateRGoodDto
                                              {
                                                  RPName = a.PName,
                                                  RPNum = a.PNum,
                                                  RSNum = a.SNum,
                                                  RUnit = a.BUnit,
                                                  RNum = c.RNum,
                                                  RBase = a.GoBit,
                                                  BNum=a. BorNum,
                                                  RTime = a.GiveTime,
                                                  RPack = c.RPack,
                                                  RDesc = c.RDesc,

                                              }
                             ).ToList()
                         }).ToList();

            var totalCount = query.Count();
            var items = query.Skip(input.SkipCount - 1).Take(input.MaxResultCount).ToList();
            //var dtos = ObjectMapper.Map<List<BorrowM>, List<BorrowDto>>(items);
            return new PagedResultDto<RGoodDto>(totalCount, query);
        }


    }
}
